package com.basker.pisces.core.meta;

import java.sql.JDBCType;

import org.springframework.util.StringUtils;

import com.basker.pisces.core.jdbc.JdbcTypeMapper;
import com.basker.pisces.core.utils.ConvertUtils;

public class DataField extends AbstractField implements IDataField {

    private final String dbFieldName;
    private String hostTableName;
    private final Class<?> fieldClass;
    private final boolean pkField;
    private final JDBCType jdbcType;
    private final boolean indexField;
    private Integer length;
    private Integer scale;
    private boolean cData = false;
    private int sort = 0;
    private String description;

    public DataField(String name, String displayName, String dbFieldName, Class<?> fieldClass) {
        this(name, displayName, dbFieldName, null, false, false, fieldClass, null);
    }

    public DataField(String name, String displayName, String dbFieldName, Class<?> fieldClass, boolean pkField,
                     boolean indexField) {
        this(name, displayName, dbFieldName, null, pkField, indexField, fieldClass, null);
    }

    public DataField(String name, String displayName, String dbFieldName, String hostTableName, boolean pkField,
                     boolean indexField, Class<?> fieldClass, JDBCType jdbcType) {
        super(name, displayName);

        this.dbFieldName = dbFieldName;
        this.hostTableName = hostTableName;
        this.pkField = pkField;
        this.indexField = indexField;
        this.fieldClass = fieldClass;

        if (jdbcType == null || jdbcType == JDBCType.NULL) {
            jdbcType = JdbcTypeMapper.getJDBCType(fieldClass);
        }

        this.jdbcType = jdbcType;
    }

    public DataField(String name, String displayName, String dbFieldName, String hostTableName, Class<?> fieldClass) {
        this(name, displayName, dbFieldName, hostTableName, false, false, fieldClass, null);
    }

    @Override
    public String getDbFieldName() {
        return dbFieldName;
    }

    @Override
    public String getDescription() {
        return description;
    }

    @Override
    public Class<?> getFieldClass() {
        return fieldClass;
    }

    @Override
    public String getHostTableName() {
        return hostTableName;
    }

    @Override
    public JDBCType getJDBCType() {
        return jdbcType;
    }

    @Override
    public int getJDBCTypeNumber() {
        return jdbcType.getVendorTypeNumber();
    }

    @Override
    public Integer getLength() {
        return length;
    }

    @Override
    public Integer getScale() {
        return scale;
    }

    @Override
    public int getSort() {
        return sort;
    }

    @Override
    public boolean isCData() {
        return cData;
    }

    @Override
    public boolean isIndexField() {
        return indexField;
    }

    @Override
    public boolean isPkField() {
        return pkField;
    }

    public void setCData(boolean cData) {
        this.cData = cData;
    }

    public void setDescription(String description) {
        this.description = description;
    }

    @Override
    public void setHostTableName(String hostTableName) {
        this.hostTableName = hostTableName;
    }

    public void setLength(Integer length) {
        this.length = length;
    }

    public void setScale(Integer scale) {
        this.scale = scale;
    }

    public void setSort(int sort) {
        this.sort = sort;
    }

    @Override
    public void setValue(Object dataObject, Object value) {
        Object resovledValue = ConvertUtils.convert(value, this.getFieldClass());
        super.setValue(dataObject, resovledValue);
    }

    @Override
    public String toString() {
        String ret = !StringUtils.isEmpty(this.hostTableName) ? this.hostTableName + "." + this.name : this.name;
        ret += (" type:" + this.fieldClass.getSimpleName());

        return "[" + ret + "]";
    }
}
